package com.example.domain.repository;

import com.example.domain.entity.PricingRule;
import com.example.domain.entity.enums.PricingRuleType;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.Pageable;
import org.springframework.data.jpa.repository.JpaRepository;
import org.springframework.data.jpa.repository.Query;
import org.springframework.data.repository.query.Param;
import org.springframework.stereotype.Repository;

import java.time.LocalDateTime;
import java.util.List;
import java.util.Optional;

/**
 * 促销规则Repository
 * 
 * @author Means
 * @since 2025-10-27
 */
@Repository
public interface PricingRuleRepository extends JpaRepository<PricingRule, String> {
    
    // ========== 基础查询 ==========
    
    /**
     * 查询未删除的促销规则列表
     * 
     * @param isDeleted 是否删除
     * @return 促销规则列表
     */
    List<PricingRule> findByIsDeleted(Boolean isDeleted);
    
    /**
     * 根据规则类型查询未删除的促销规则
     * 
     * @param type 规则类型
     * @param isDeleted 是否删除
     * @return 促销规则列表
     */
    List<PricingRule> findByTypeAndIsDeleted(PricingRuleType type, Boolean isDeleted);
    
    /**
     * 根据启用状态查询未删除的促销规则
     * 
     * @param enabled 是否启用
     * @param isDeleted 是否删除
     * @return 促销规则列表
     */
    List<PricingRule> findByEnabledAndIsDeleted(Boolean enabled, Boolean isDeleted);
    
    /**
     * 根据规则类型和启用状态查询未删除的促销规则
     * 
     * @param type 规则类型
     * @param enabled 是否启用
     * @param isDeleted 是否删除
     * @return 促销规则列表
     */
    List<PricingRule> findByTypeAndEnabledAndIsDeleted(PricingRuleType type, Boolean enabled, Boolean isDeleted);
    
    // ========== 时间范围查询 ==========
    
    /**
     * 查询指定时间点生效的促销规则
     * 
     * @param currentTime 当前时间
     * @param enabled 是否启用
     * @param isDeleted 是否删除
     * @return 促销规则列表
     */
    @Query("SELECT r FROM PricingRule r WHERE r.enabled = :enabled " +
           "AND r.validFrom <= :currentTime " +
           "AND (r.validTo IS NULL OR r.validTo > :currentTime) " +
           "AND r.isDeleted = :isDeleted " +
           "ORDER BY r.priority DESC, r.validFrom DESC")
    List<PricingRule> findEffectiveRules(@Param("currentTime") LocalDateTime currentTime,
                                        @Param("enabled") Boolean enabled,
                                        @Param("isDeleted") Boolean isDeleted);
    
    /**
     * 查询指定时间点、指定类型的生效促销规则
     * 
     * @param type 规则类型
     * @param currentTime 当前时间
     * @param enabled 是否启用
     * @param isDeleted 是否删除
     * @return 促销规则列表
     */
    @Query("SELECT r FROM PricingRule r WHERE r.type = :type " +
           "AND r.enabled = :enabled " +
           "AND r.validFrom <= :currentTime " +
           "AND (r.validTo IS NULL OR r.validTo > :currentTime) " +
           "AND r.isDeleted = :isDeleted " +
           "ORDER BY r.priority DESC, r.validFrom DESC")
    List<PricingRule> findEffectiveRulesByType(@Param("type") PricingRuleType type,
                                               @Param("currentTime") LocalDateTime currentTime,
                                               @Param("enabled") Boolean enabled,
                                               @Param("isDeleted") Boolean isDeleted);
    
    /**
     * 查询指定时间范围内的促销规则
     * 
     * @param startTime 开始时间
     * @param endTime 结束时间
     * @param isDeleted 是否删除
     * @return 促销规则列表
     */
    @Query("SELECT r FROM PricingRule r WHERE " +
           "r.validFrom <= :endTime " +
           "AND (r.validTo IS NULL OR r.validTo >= :startTime) " +
           "AND r.isDeleted = :isDeleted " +
           "ORDER BY r.priority DESC, r.validFrom DESC")
    List<PricingRule> findByValidDateRange(@Param("startTime") LocalDateTime startTime,
                                          @Param("endTime") LocalDateTime endTime,
                                          @Param("isDeleted") Boolean isDeleted);
    
    // ========== 分页查询 ==========
    
    /**
     * 分页查询未删除的促销规则
     * 
     * @param isDeleted 是否删除
     * @param pageable 分页参数
     * @return 促销规则分页结果
     */
    Page<PricingRule> findByIsDeleted(Boolean isDeleted, Pageable pageable);
    
    /**
     * 根据规则类型分页查询未删除的促销规则
     * 
     * @param type 规则类型
     * @param isDeleted 是否删除
     * @param pageable 分页参数
     * @return 促销规则分页结果
     */
    Page<PricingRule> findByTypeAndIsDeleted(PricingRuleType type, Boolean isDeleted, Pageable pageable);
    
    // ========== 自定义查询 ==========
    
    /**
     * 根据ID查询未删除的促销规则
     * 
     * @param id 规则ID
     * @return 促销规则对象
     */
    @Query("SELECT r FROM PricingRule r WHERE r.id = :id AND r.isDeleted = false")
    Optional<PricingRule> findByIdAndNotDeleted(@Param("id") String id);
    
    /**
     * 查询所有当前生效的促销规则（已启用且未删除且在有效期内）
     * 
     * @return 促销规则列表
     */
    @Query("SELECT r FROM PricingRule r WHERE r.enabled = true " +
           "AND r.validFrom <= CURRENT_TIMESTAMP " +
           "AND (r.validTo IS NULL OR r.validTo > CURRENT_TIMESTAMP) " +
           "AND r.isDeleted = false " +
           "ORDER BY r.priority DESC, r.type, r.validFrom DESC")
    List<PricingRule> findAllCurrentEffectiveRules();
    
    /**
     * 查询指定类型、指定优先级、指定启用状态的规则
     * 用于促销规则的排他性检查（确保同一优先级不会有冲突规则）
     * 
     * @param type 规则类型
     * @param priority 优先级
     * @param enabled 是否启用
     * @param isDeleted 是否删除
     * @return 规则列表
     */
    List<PricingRule> findByTypeAndPriorityAndEnabledAndIsDeleted(
            PricingRuleType type, 
            Integer priority, 
            Boolean enabled, 
            Boolean isDeleted
    );
}

